<?php

use Mapper\MemberModel as MemberMapper;
use Mapper\SparringbuysModel as BuyMapper;
use Mapper\SparringbuydetailModel as BuyDetailMapper;
use Mapper\SparringgameModel as GameMapper;

class SparringbuysController extends \Base\ApiController {

    /**
     * @desc 看大腿列表
     */
    public function publishListAction() {
        $request = $this->getRequest();
        $page    = (int)$request->get('page', 1);
        $perPage = (int)$request->get('per_page', 15);
        $page    = max(1, $page);
        $perPage = min(30, $perPage);
        $limit   = $perPage;
        $offset  = $limit * ($page - 1);
        $return  = [];

        $buyDetailMapper = BuyDetailMapper::getInstance();
        $where           = ['status' => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL, 'begin_time > ?' => time()];
        $models          = $buyDetailMapper->group($where, null, 'sparring_buy_id', 'begin_time', $limit, $offset);

        if(empty($models)) {
            return \Response::data([], '看大腿列表为空');
        }

        $memberMapper = MemberMapper::getInstance();
        $buyMapper    = BuyMapper::getInstance();
        $gameMapper   = GameMapper::getInstance();

        foreach($models as $model) {
            $arr                  = $model->toArray();
            $arr['time_interval'] = date('H:i', $model->getBegin_time()) . '-' . date('H:i', $model->getEnd_time());
            $buyId                = $model->getSparring_buy_id();
            $sprBuyModel          = $buyMapper->findById($buyId);
            $memberModel          = $memberMapper->findById($sprBuyModel->getUid());

            if(!$memberModel instanceof \MemberModel) {
                $arr['nickname'] = '';
                $arr['avatar']   = '';
            } else {
                $arr['nickname'] = urldecode($memberModel->getNick_name());
                $arr['avatar']   = $memberModel->getAvatar();
            }

            $gameModel = $gameMapper->findById($model->getGame_id());

            if(!$gameModel instanceof \SparringGameModel) {
                $arr['game_name'] = '';
            } else {
                $arr['game_name'] = $gameModel->getGame_name();
            }

            $return[] = $arr;
        }

        return \Response::data($return);
    }

    /**
     * @desc 看大腿发布接口
     *
     * @return false
     */
    public function publishAction() {
        $request    = $this->getRequest();
        $uid        = \Lib\User::getInstance()->id();
        $gameId     = (int)$request->get('game_id');
        $netBar     = (string)$request->get('net_bar');
        $price      = (float)$request->get('price', 0.00);
        $beginTime  = (string)$request->get('begin_time');
        $endTime    = (string)$request->get('end_time');
        $gameLevel  = (string)$request->get('game_level');
        $gameServer = (string)$request->get('game_server');
        $manifesto  = (string)$request->get('manifesto');

        if($gameId <= 0) {
            return \Response::error('游戏名不能为空', 10201);
        }

        if($price <= 0) {
            return \Response::error('价格数字有误', 10202);
        }

        $beginTime = strtotime($beginTime);

        if(empty($beginTime)) {
            return \Response::error('空闲的开始时间不能为空', 10203);
        }

        $endTime = strtotime($endTime);

        if(empty($endTime)) {
            return \Response::error('空闲的结束时间不能为空', 10204);
        }

        if($endTime < $beginTime || $beginTime < time() + 600) {
            return \Response::error('时间无效, 请重新选择', 10219);
        }

        // 同一用户同一时间段只能发布一条信息
        $buyMapper = BuyMapper::getInstance();

        $beginTimeModel = $buyMapper->fetch([
            'uid'             => $uid,
            'begin_time <= ?' => $beginTime,
            'end_time > ?'    => $beginTime,
            'status'          => \Lib\Consts::SPARRING_BUY_STATUS_NORMAL
        ]);
        $endTimeModel   = $buyMapper->fetch([
            'uid'             => $uid,
            'begin_time <= ?' => $endTime,
            'end_time > ?'    => $endTime,
            'status'          => \Lib\Consts::SPARRING_BUY_STATUS_NORMAL
        ]);

        if(!empty($beginTimeModel) || !empty($endTimeModel)) {
            return \Response::error('当前时间区段中含有已发布信息', 10220);
        }

        $buyModel = new \SparringBuysModel();
        $buyModel->setUid($uid);
        $buyModel->setBegin_time($beginTime);
        $buyModel->setEnd_time($endTime);
        $buyModel->setAdd_time(time());
        $buyModel->setStatus(\Lib\Consts::SPARRING_BUY_STATUS_NORMAL);

        $buyMapper->begin();
        $buyId = $buyMapper->insert($buyModel);

        if($buyId <= 0) {
            $buyMapper->rollback();
            return \Response::error('发布失败, 请重试', 10212);
        }

        $memberMapper = MemberMapper::getInstance();
        $memberModel  = $memberMapper->findById($uid);

        // 时间区段
        $timeInterval   = $this->getTimeInterval($beginTime, $endTime);
        $sprDetailModel = new \SparringBuyDetailModel();

        foreach($timeInterval as $value) {
            $sprDetailModel->setSparring_buy_id($buyId);
            $sprDetailModel->setBegin_time($value[0]);
            $sprDetailModel->setEnd_time($value[1]);
            $sprDetailModel->setGame_id($gameId);
            $sprDetailModel->setNet_bar($netBar);
            $sprDetailModel->setPrice($price);
            $sprDetailModel->setGame_level($gameLevel);
            $sprDetailModel->setGame_server($gameServer);
            $sprDetailModel->setManifesto($manifesto);
            $sprDetailModel->setStatus(\Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL);
            $sprDetailModel->setAdd_time(time());
            $sprDetailModel->setGender($memberModel->getGender());

            $buyDetailMapper = BuyDetailMapper::getInstance();

            try {
                $lastId = $buyDetailMapper->insert($sprDetailModel);
            } catch(\Exception $e) {
                $lastId = 0;
            }

            if($lastId <= 0) {
                $buyMapper->rollback();
                return \Response::error('发布详情数据失败, 请重试', 10213);
            }
        }

        $buyMapper->commit();
        return \Response::data(null, '发布成功');
    }

    /**
     * @desc 编辑看大腿发布信息
     *
     * @return false
     */
    public function publishEditAction() {
        $request    = $this->getRequest();
        $uid        = \Lib\User::getInstance()->id();
        $buyId      = (int)$request->get('buy_id');
        $gameId     = (int)$request->get('game_id');
        $netBar     = (string)$request->get('net_bar');
        $price      = (float)$request->get('price', 0.00);
        $gameLevel  = (string)$request->get('game_level');
        $gameServer = (string)$request->get('game_server');
        $manifesto  = (string)$request->get('manifesto');

        if($buyId <= 0) {
            return \Response::error('看大腿id值有误', 10208);
        }

        $buyMapper = BuyMapper::getInstance();
        $model     = $buyMapper->fetch(['uid' => $uid, 'id' => $buyId]);

        if(!$model instanceof \SparringBuysModel) {
            return \Response::error('Invalid BuyId', 10211);
        }

        if($gameId <= 0) {
            return \Response::error('游戏名不能为空', 10201);
        }

        if($price <= 0) {
            return \Response::error('价格数字有误', 10202);
        }

        $buyDetailMapper = BuyDetailMapper::getInstance();
        $detailModels    = $buyDetailMapper->fetchAll([
            'sparring_buy_id' => $buyId,
            'status'          => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL,
            'begin_time > ?'  => time(),
        ]);

        if(empty($detailModels)) {
            return \Response::error('Invalid BuyId', 10211);
        }

        $data = [
            'game_id'     => $gameId,
            'net_bar'     => $netBar,
            'price'       => $price,
            'game_level'  => $gameLevel,
            'game_server' => $gameServer,
            'manifesto'   => $manifesto,
            'update_time' => time(),
        ];

        try {
            $rows = $buyDetailMapper->update($data, [
                'sparring_buy_id' => $buyId,
                'status'          => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL,
                'begin_time > ?'  => time(),
            ]);
            return $rows > 0 ? \Response::data(null) : \Response::error('看大腿信息编辑失败', 10228);
        } catch(\Exception $exc) {
            return \Response::error('异常信息报错', 10100);
        }
    }

    /**
     * @desc 看大腿发布的信息详情
     *
     * @return false
     */
    public function publishDetailAction() {
        $request = $this->getRequest();
        $buyId   = (int)$request->get('buy_id', 0);

        if(empty($buyId)) {
            return \Response::error('看大腿id值有误', 10208);
        }

        $buyMapper = BuyMapper::getInstance();
        $model     = $buyMapper->findById($buyId);

        if(!$model instanceof \SparringBuysModel) {
            return \Response::error('Invalid BuyId', 10211);
        }

        if($model->getEnd_time() < time()) {
            return \Response::data([]);
        }

        $buyDetailMapper = BuyDetailMapper::getInstance();

        // 需求关系, 将其数据先死定为最后一个时间段的信息详情, 后续再改
        $detailModels = $buyDetailMapper->fetchAll(['sparring_buy_id' => $buyId]);

        if(empty($detailModels)) {
            return \Response::error('看大腿id值有误', 10208);
        }

        $count        = count($detailModels);
        $return       = $detailModels[$count - 1]->toArray();
        $memberMapper = MemberMapper::getInstance();
        $gameMapper   = GameMapper::getInstance();

        foreach($detailModels as $detailModel) {
            if($detailModel->getBegin_time() > time()
                && $detailModel->getStatus() === 1 || $detailModel->getStatus() === 2
            ) {
                $return['time_interval'][] = [
                    $detailModel->getId(),
                    date('H:i', $detailModel->getBegin_time()) . '-' . date('H:i', $detailModel->getEnd_time()),
                    $detailModel->getStatus(),
                ];
            }

            $uid         = $model->getUid();
            $memberModel = $memberMapper->findById($uid);

            if(!$memberModel instanceof \MemberModel) {
                return \Response::error('Invalid Uid', 10229);
            }

            $return['uid']      = $uid;
            $return['avatar']   = $memberModel->getAvatar();
            $return['nickname'] = urldecode($memberModel->getNick_name());

            $gameModel = $gameMapper->findById($detailModel->getGame_id());

            if(!$gameModel instanceof \SparringGameModel) {
                $return['game_name'] = '';
            } else {
                $return['game_name'] = $gameModel->getGame_name();
            }
        }

        return \Response::data($return);
    }

    /**
     * @desc 获取时间区段
     *
     * @param     $beginTime
     * @param     $endTime
     * @param int $interval
     * @return array
     */
    public function getTimeInterval($beginTime, $endTime, $interval = 3600) {
        $timeArr      = [];
        $timeInterval = $endTime - $beginTime;
        $num          = floor($timeInterval / $interval);
        $remainder    = $timeInterval % $interval;

        for($i = 0; $i < $num; $i++) {
            $timeArr[] = [$beginTime + $i * $interval, $beginTime + $interval * ($i + 1)];
        }

        if($remainder !== 0) {
            $timeArr[] = [$beginTime + $i * $interval, $endTime];
        }

        return $timeArr;
    }

    /**
     * @desc 看大腿搜索功能
     *
     * @return false
     */
    public function searchAction() {
        $request = $this->getRequest();
        $search  = $request->get('search', '');
        $type    = (string)$request->get('type', 'nickname');
        $page    = (int)$request->get('page', 1);
        $perPage = (int)$request->get('per_page', 15);
        $page    = max(1, $page);
        $perPage = min(30, $perPage);
        $limit   = $perPage;
        $offset  = $limit * ($page - 1);
        $ids     = [];
        $return  = [];

        if(empty($search)) {
            return \Response::error('搜索文字不能为空', 10210);
        }

        $buyMapper    = BuyMapper::getInstance();
        $memberMapper = MemberMapper::getInstance();

        if($type === 'nickname') {
            $search      = urlencode($search);
            $memberModel = $memberMapper->findByNick_name($search);

            if(!$memberModel instanceof \MemberModel) {
                return \Response::data([], '昵称搜索结果为空');
            }

            $uid = $memberModel->getId();
        } elseif($type === 'uid') {
            $uidStr = strlen($search);

            if((int)$search < 65535 || $uidStr < 5 || $uidStr > 10) {
                return \Response::data([], 'Uid搜索结果为空');
            }

            $memberModel = $memberMapper->findById($search);

            if(!$memberModel instanceof \MemberModel) {
                return \Response::data([], 'Uid搜索结果为空');
            }

            $uid = $search;
        } else {
            return \Response::error('搜索类型有误', 10222);
        }

        $sprBuyModels = $buyMapper->fetchAll([
            'uid'          => $uid,
            'end_time > ?' => time(),
        ], 'add_time DESC', $limit, $offset);

        if(empty($sprBuyModels)) {
            return \Response::data([], '搜索结果为空');
        }

        foreach($sprBuyModels as $sprBuyModel) {
            $ids[] = $sprBuyModel->getId();
        }

        $buyDetailMapper    = BuyDetailMapper::getInstance();
        $sprBuyDetailModels = $buyDetailMapper->group([
            'sparring_buy_id' => $ids,
            'status'          => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL,
            'begin_time > ?'  => time(),
        ], null, 'sparring_buy_id', 'begin_time', $limit, $offset);

        if(empty($sprBuyDetailModels)) {
            return \Response::data([], '搜索结果为空');
        }

        $memberMapper = MemberMapper::getInstance();

        foreach($sprBuyDetailModels as $sprBuyDetailModel) {
            $arr                  = $sprBuyDetailModel->toArray();
            $arr['time_interval'] = date('H:i', $sprBuyDetailModel->getBegin_time()) . '-' . date('H:i', $sprBuyDetailModel->getEnd_time());
            $memberModel          = $memberMapper->findById($uid);

            if(!$memberModel instanceof \MemberModel) {
                $arr['nickname'] = '';
            }

            $arr['nickname'] = urldecode($memberModel->getNick_name());
            $return[]        = $arr;
        }

        return \Response::data($return, '搜索成功');
    }

    /**
     * @desc 我的发布-看大腿列表
     */
    public function myPublishListAction() {
        $request = $this->getRequest();
        $uid     = \Lib\User::getInstance()->id();
        $page    = (int)$request->get('page', 1);
        $perPage = (int)$request->get('per_page', 5);
        $page    = max(1, $page);
        $perPage = min(30, $perPage);
        $limit   = $perPage;
        $offset  = $limit * ($page - 1);

        $buyMapper = BuyMapper::getInstance();
        // 排序按照开始时间倒序
        $sprBuyModels = $buyMapper->fetchAll(['uid' => $uid], 'begin_time DESC', $limit, $offset);
        $return       = [];

        if(empty($sprBuyModels)) {
            return \Response::data([], '看大腿列表为空');
        }

        $ids = [];

        foreach($sprBuyModels as $sprBuyModel) {
            $buyId = $sprBuyModel->getId();
            $ids[] = $buyId;
            $data  = $this->getStatusData($buyId);

            if(!empty($data)) {
                $return[] = $data;
            }
        }

        return \Response::data($return);
    }

    /**
     * @desc  我的发布-看大腿信息删除(可编辑的才可删除)
     * @return false
     */
    public function myPublishDelAction() {
        $request = $this->getRequest();
        $uid     = \Lib\User::getInstance()->id();
        $buyId   = (int)$request->get('buy_id', 0);

        $buyMapper = BuyMapper::getInstance();
        $model     = $buyMapper->fetch(['id' => $buyId, 'uid' => $uid]);

        if(!$model instanceof \SparringBuysModel) {
            return \Response::error('看大腿信息id不存在', 10205);
        }

        $buyDetailMapper = BuyDetailMapper::getInstance();

        $detailModel = $buyDetailMapper->fetch([
            'sparring_buy_id' => $buyId,
            'status'          => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL]);

        if(!$detailModel instanceof \SparringBuyDetailModel) {
            return \Response::error('看大腿信息不存在', 10215);
        }

        $buyMapper->begin();
        $data = [
            'status' => \Lib\Consts::SPARRING_BUY_STATUS_DEL,
        ];

        try {
            $rows = $buyMapper->update($data, [
                'id'     => $buyId,
                'uid'    => $uid,
                'status' => \Lib\Consts::SPARRING_BUY_STATUS_NORMAL,
            ]);
        } catch(\Exception $e) {
            $rows = 0;
        }

        if($rows <= 0) {
            $buyMapper->rollback();
            return \Response::error('看大腿信息删除失败', 10227);
        }

        try {
            $rows = $buyDetailMapper->update(
                ['status' => \Lib\Consts::SPARRING_DETAIL_STATUS_DEL],
                [
                    'sparring_buy_id' => $buyId,
                    'status'          => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL,
                ]);
        } catch(\Exception $exc) {
            $rows = 0;
        }

        if($rows <= 0) {
            $buyMapper->rollback();
            return \Response::error('看大腿信息删除失败', 10227);
        }

        $buyMapper->commit();
        return \Response::data(null);
    }


    /**
     * @desc 通过看大腿发布信息的id取得对应的3种状态详情
     * @param int $buyId
     * @return array|false
     */
    public function getStatusData($buyId = 0) {
        if($buyId <= 0) {
            return [];
        }

        $buyMapper = BuyMapper::getInstance();
        $sprModel  = $buyMapper->findById($buyId);

        if(!$sprModel instanceof \SparringBuysModel) {
            return \Response::error('看大腿信息id不存在', 10205);
        }

        // 已过期
        $delayWhere = ['sparring_buy_id' => $buyId, 'begin_time <= ' . time(), 'status' => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL];
        // 显示中
        $normalWhere = ['sparring_buy_id' => $buyId, 'begin_time > ' . time(), 'status' => \Lib\Consts::SPARRING_DETAIL_STATUS_NORMAL];
        // 被接单
        $orderWhere = ['sparring_buy_id' => $buyId, 'status' => \Lib\Consts::SPARRING_DETAIL_STATUS_PAY];

        $buyDetailMapper = BuyDetailMapper::getInstance();
        $gameMapper      = GameMapper::getInstance();
        $delayModel      = $buyDetailMapper->fetch($delayWhere);
        $normalModel     = $buyDetailMapper->fetch($normalWhere);
        $orderModel      = $buyDetailMapper->fetch($orderWhere);

        $return = [];

        if($delayModel instanceof \SparringBuyDetailModel) {
            $delayData                   = $delayModel->toArray();
            $delayData['interval_count'] = $buyDetailMapper->count($delayWhere, 'id');
            $delayData['time_interval']  = date('H:i', $delayModel->getBegin_time()) . '-' . date('H:i', $delayModel->getEnd_time());

            $gameModel = $gameMapper->findById($delayModel->getGame_id());

            if(!$gameModel instanceof \SparringGameModel) {
                $delayData['game_name'] = '';
            } else {
                $delayData['game_name'] = $gameModel->getGame_name();
            }

            $return['delay']             = $delayData;
            $return['date']              = date('Y年m月d日', $sprModel->getAdd_time());
        }

        if($normalModel instanceof \SparringBuyDetailModel) {
            $normalData                   = $normalModel->toArray();
            $normalData['interval_count'] = $buyDetailMapper->count($normalWhere, 'id');
            $normalData['time_interval']  = date('H:i', $normalModel->getBegin_time()) . '-' . date('H:i', $normalModel->getEnd_time());

            $gameModel = $gameMapper->findById($normalModel->getGame_id());

            if(!$gameModel instanceof \SparringGameModel) {
                $normalData['game_name'] = '';
            } else {
                $normalData['game_name'] = $gameModel->getGame_name();
            }

            $return['normal']             = $normalData;
            $return['date']               = date('Y年m月d日', $sprModel->getAdd_time());
        }

        if($orderModel instanceof \SparringBuyDetailModel) {
            $orderData                   = $orderModel->toArray();
            $orderData['interval_count'] = $buyDetailMapper->count($orderWhere, 'id');
            $orderData['time_interval']  = date('H:i', $orderModel->getBegin_time()) . '-' . date('H:i', $orderModel->getEnd_time());

            $gameModel = $gameMapper->findById($orderModel->getGame_id());

            if(!$gameModel instanceof \SparringGameModel) {
                $orderData['game_name'] = '';
            } else {
                $orderData['game_name'] = $gameModel->getGame_name();
            }

            $return['order']             = $orderData;
            $return['date']              = date('Y年m月d日', $sprModel->getAdd_time());
        }

        return $return;
    }

    /**
     * @desc 陪练游戏
     * @return false
     */
    public function sparringGameAction() {
        $mapper = GameMapper::getInstance();
        $models = $mapper->fetchAll(null, 'order DESC, id', 50);

        if(empty($models)) {
            return \Response::data([]);
        }

        return \Response::data($models, '获取陪练游戏成功');
    }

    /**
     * @desc 陪练游戏--筛选
     * @return false
     */
    public function sparringGameSelectAction() {
        $mapper = GameMapper::getInstance();
        $models = $mapper->fetchAll(['status' => 1], 'order DESC, id', 15);

        if(empty($models)) {
            return \Response::data([]);
        }

        return \Response::data($models, '获取陪练游戏成功');
    }

}
